package com.vm.common;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.io.UnsupportedEncodingException;
import java.io.Writer;
import java.sql.Timestamp;
import java.text.DecimalFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.Properties;
import java.util.Random;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import javax.servlet.http.HttpServletRequest;

import org.apache.log4j.Logger;

public class Tools {

	/**
	 * Logger for this class
	 */
	private static final Logger _log = Logger.getLogger(Tools.class);

	/**
	 * 对文件大小进行转�?
	 * 
	 * @param len
	 * @return
	 */
	public static String dataLengthFormat(long len) {
		String str = "";

		if (len < 1024) {
			str = len + " Byte";
		} else if (len >= 1024 && len < 1024 * 1024) {
			float f = (new Float(len)).floatValue() / (new Float(1024)).floatValue();
			str = Tools.floatFormat(f) + " KB";
		} else if (len >= 1024 * 1024) {
			float f = (new Float(len)).floatValue() / (new Float(1024 * 1024)).floatValue();
			str = Tools.floatFormat(f) + " M";
		}

		return str;
	}

	/**
	 * 生成指定长度的数字随机码
	 * 
	 * @param length 长度
	 * @return
	 */
	public static String getRandomString(int length) {
		Random random = new Random();
		StringBuffer bf = new StringBuffer();
		for (int i = 0; i < length; i++) {
			bf.append(random.nextInt(9));
		}
		return bf.toString();
	}

	/**
	 * 格式化floag
	 * 
	 * @param value
	 * @return
	 */
	public static String floatFormat(float value) {
		DecimalFormat formater = new DecimalFormat("0.00");
		return formater.format(value);
	}

	/**
	 * 自定义格式化float
	 * 
	 * @param value
	 * @param format
	 * @return
	 */
	public static String floatFormat(float value, String format) {
		DecimalFormat formater = new DecimalFormat(format);
		return formater.format(value);
	}

	public static String fckHtmlDecode(String str) {
		if (str == null) return "";
		str = str.replaceAll("&lt;", "<");
		str = str.replaceAll("&gt;", ">");
		str = str.replaceAll("&quot;", "\"");
		return str;
	}

	public static String fckHtmlEncode(String str) {
		if (str == null) return "";
		str = str.replaceAll("<", "&lt;");
		str = str.replaceAll(">", "&gt;");
		str = str.replaceAll("\"", "&quot;");

		return str;
	}

	/**
	 * 把从表单接到的字符里的html反解�?
	 * 
	 * @param str
	 * @return
	 */
	public static String htmlDecode(String str) {
		if (str == null) return "";
		str = str.replaceAll("&lt;", "<");
		str = str.replaceAll("&gt;", ">");
		str = str.replaceAll("&quot;", "\"");
		// str = str.replaceAll("&amp", "&");
		return str;
	}

	/**
	 * 对html编码,显示在网页的textarea里不会让html乱码
	 * 
	 * @param str
	 * @return
	 */
	public static String htmlEncode(String str) {
		if (str == null) return "";
		// str = str.replaceAll("&", "&amp");
		str = str.replaceAll("<", "&lt;");
		str = str.replaceAll(">", "&gt;");
		str = str.replaceAll("\"", "&quot;");

		return str;
	}

	/**
	 * 替换回车�?
	 * 
	 * @param str
	 * @return
	 */
	public static String moreCodeEncodeBr(String str) {
		if (str == null) return "";
		str = str.replaceAll("\r\n", "");
		str = str.replaceAll("\r", "");
		str = str.replaceAll("\n", "");
		return str;
	}
	/**
	 * 当前�?
	 * @return
	 */
	public static String getNowYEAR(){
		Calendar cal = Calendar.getInstance(); 
		int year = cal.get(Calendar.YEAR); 
        return year+"";
	}

	/**
	 * 替换回车符和空格为html
	 * 
	 * @param str
	 * @return
	 */
	public static String moreCodeEncode(String str) {
		if (str == null) return "";
		str = str.replaceAll("\r\n", "<br/>");
		str = str.replaceAll("\r", "<br/>");
		str = str.replaceAll("\n", "<br/>");
		// str = str.replaceAll("&", "&amp");
		str = str.replaceAll(" ", "&nbsp;");
		return str;
	}

	/**
	 * 替换回车符和空格为对应的�?
	 * 
	 * @param str
	 * @return
	 */
	public static String moreCodeDecode(String str) {
		if (str == null) return "";
		str = str.replaceAll("<br/>", "\r\n");
		str = str.replaceAll("&nbsp;", " ");
		// str = str.replaceAll("&amp", "&");
		return str;
	}

	/**
	 * Exception 以字符的方式输出
	 * 
	 * @param e
	 * @return 错误信息string
	 */
	public static String exceptionToString(Exception e) {
		Writer writer = new StringWriter();
		PrintWriter print = new PrintWriter(writer);
		e.printStackTrace(print);
		String result = writer.toString();
		try {
			writer.close();
		} catch (IOException e1) {
		} finally {
			if (print != null) {
				print.close();
			}
		}
		return result;
	}

	/**
	 * 把str转成date
	 * 
	 * @param str yyyy-MM-dd,HH:mm:ss,yyyy-MM-dd HH:mm:ss 三种格式
	 * @return date,出错则返回当前时�?
	 */
	public static Date stringToDate(String str) {
		if (str == null || str.length() == 0) return null;
		java.text.SimpleDateFormat da = null;
		if (str.indexOf(":") == -1) {
			da = new java.text.SimpleDateFormat("yyyy-MM-dd");
		} else if (str.indexOf("-") == -1) {
			da = new java.text.SimpleDateFormat("HH:mm:ss");
		} else {
			da = new java.text.SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
		}

		Date date = null;

		try {
			date = da.parse(str);
		} catch (ParseException e) {
			_log.error("", e);
		}
		return date;
	}
	/**
	 * 将Timestamp转换成String
	 * @param time
	 * @param format 
	 * @return
	 */
	public static String formatDateToString(Timestamp time,String format){
		SimpleDateFormat df = new SimpleDateFormat(format);//定义格式 
		return df.format(time);

	}

	/**
	 * 得到格式化时间的毫秒
	 * 
	 * @param str
	 * @param format
	 * @return
	 */
	public static long stringToMillisecond(String str, String format) {
		if (str == null || str.length() == 0) return 0;
		java.text.SimpleDateFormat da = new java.text.SimpleDateFormat(format);

		try {
			return da.parse(str).getTime();
		} catch (ParseException e) {
			_log.error("", e);
		}
		return 0;
	}

	/**
	 * 格式化日期，如果出错，则抛出 MessageException
	 * 
	 * @param str
	 * @return
	 * @throws MessageException
	 */
	public static Date stringToDateTry(String str) throws Exception {

		java.text.SimpleDateFormat da = null;
		if (str.indexOf(":") == -1) {
			da = new java.text.SimpleDateFormat("yyyy-MM-dd");
		} else if (str.indexOf("-") == -1) {
			da = new java.text.SimpleDateFormat("HH:mm:ss");
		} else {
			da = new java.text.SimpleDateFormat("yyyy-MM-dd HH:mm");
		}

		try {
			return da.parse(str);
		} catch (ParseException e) {
			_log.error("", e);
			throw e;
		}
	}

	/**
	 * 判断�?��字符是否是数�?正负�?
	 * 
	 * @param str 要判断的字符�?
	 * @param len �?��长度，超过了此长度既默认为非数字
	 * @return 是数字返回true
	 */
	public static boolean isN(String str, int len) {
		if (str == null) {
			return false;
		}

		Pattern p = Pattern.compile("(\\-{0,1})([0-9]{1," + len + "})");
		Matcher m = p.matcher(str);

		if (m.matches()) {
			return true;
		}
		return false;
	}

	/**
	 * 判断�?��字符是否是数�?正负�?，最长为19�?
	 * 
	 * @param str
	 * @return
	 */
	public static boolean isN(String str) {
		if (str == null) {
			return false;
		}

		Pattern p = Pattern.compile("(\\-{0,1})([0-9]{1,19})");
		Matcher m = p.matcher(str);

		if (m.matches()) {
			return true;
		}
		return false;
	}

	public static Properties loadProperties(String path, String encode) {
		FileInputStream in = null;
		InputStreamReader inRead = null;
		Properties config = new Properties();
		try {
			in = new FileInputStream(path);
			inRead = new InputStreamReader(in, encode);
			config.load(inRead);
		} catch (Exception e) {
			_log.error("", e);
		} finally {
			if (in != null) {
				try {
					in.close();
				} catch (IOException e) {
				}
			}
			if (inRead != null) {
				try {
					inRead.close();
				} catch (IOException e) {
				}
			}
		}
		return config;
	}

	/**
	 * 加载properties文件
	 * 
	 * @param path
	 * @return
	 */
	public static Properties loadProperties(String path) {
		Properties properties = new Properties();
		InputStream in = Tools.class.getResourceAsStream(path);

		try {
			properties.load(in);
		} catch (IOException e) {
			_log.error("", e);
		} finally {
			if (in != null) {
				try {
					in.close();
				} catch (IOException e) {
				}
			}
		}
		return properties;
	}

	public static String readFileNoTry(String path) throws Exception {

		StringBuffer sbf = new StringBuffer();

		File f = new File(path);
		if (!f.exists() || !f.isFile()) {
			return null;
		}
		FileReader fr = null;
		BufferedReader bf = null;
		try {
			fr = new FileReader(f);
			bf = new BufferedReader(fr);
			String line = bf.readLine();
			while (line != null) {
				sbf.append(line).append("\r\n");
				line = bf.readLine();
			}
		} catch (IOException e) {
			_log.error("", e);
			throw e;
		} finally {
			if (fr != null) {
				try {
					fr.close();
				} catch (IOException e) {
				}
			}
			if (bf != null) {
				try {
					bf.close();
				} catch (IOException e) {
				}
			}
		}

		return sbf.toString();

	}

	/**
	 * 读取�?��指定位置的Properties文件
	 */
	public static Properties readProperties(String path) throws Exception {
		FileInputStream in = null;
		Properties properties = new Properties();
		try {
			in = new FileInputStream(path);
			properties.load(in);
		} catch (Exception e) {
			_log.error("", e);
			throw e;
		} finally {
			if (in != null) {
				try {
					in.close();
				} catch (IOException e) {
				}
			}
		}
		return properties;
	}

	/**
	 * 以默认的方式设一个文�?
	 * 
	 * @param path
	 * @param encode
	 * @return
	 * @throws MessageException
	 */
	public static String readFile(String path, String encode) throws Exception {

		StringBuffer sbf = new StringBuffer();

		File f = new File(path);
		if (!f.exists() || !f.isFile()) {
			throw new Exception("read file notfound:" + path);
		}
		FileInputStream in = null;
		InputStreamReader inRead = null;
		BufferedReader bf = null;
		try {

			in = new FileInputStream(f);
			inRead = new InputStreamReader(in, encode);
			bf = new BufferedReader(inRead);
			String line = bf.readLine();
			while (line != null) {
				sbf.append(line).append("\r\n");
				line = bf.readLine();
			}
		} catch (IOException e) {
			_log.error("", e);
			throw e;
		} finally {
			if (in != null) {
				try {
					in.close();
				} catch (IOException e) {
				}
			}
			if (inRead != null) {
				try {
					inRead.close();
				} catch (IOException e) {
				}
			}
			if (bf != null) {
				try {
					bf.close();
				} catch (IOException e) {
				}
			}
		}

		return sbf.toString();

	}

	/**
	 * 写文件，如果文件不存在则创建�?��
	 * 
	 * @param path
	 * @param value
	 * @param encode
	 * @return
	 * @throws MessageException
	 */
	public static void writeFile(String path, String value, String encode) throws Exception {

		FileOutputStream stream = null;
		OutputStreamWriter out = null;
		try {
			stream = new FileOutputStream(path);
			out = new OutputStreamWriter(stream, encode);
			out.write(value);
		} catch (UnsupportedEncodingException e) {
			_log.error("", e);
			throw e;
		} catch (FileNotFoundException e) {
			_log.error("", e);
			throw e;
		} catch (IOException e) {
			_log.error("", e);
			throw e;
		} finally {
			if (out != null) {
				try {
					out.close();
				} catch (IOException e) {
					_log.error("", e);
				}

			}
			if (stream != null) {
				try {
					stream.close();
				} catch (IOException e) {
					_log.error("", e);
				}
			}

		}
	}

	/**
	 * 读取�?��文件
	 * 
	 * @param path
	 * @param value
	 * @param iscloak false 为覆盖写,true为接�?��
	 * @return
	 * @throws MessageException
	 */
	public static boolean writeFile(String path, String value, boolean iscloak) throws Exception {
		FileWriter writer = null;
		PrintWriter print = null;
		try {
			writer = new FileWriter(path, iscloak);
			print = new PrintWriter(writer);
			print.write(value);
		} catch (IOException e) {
			_log.error("", e);
			throw e;
		} finally {
			if (writer != null) {
				try {
					writer.close();
				} catch (IOException e) {
				}
			}
			if (print != null) {
				print.close();
			}
		}
		return true;
	}

	/**
	 * 格式化时�?
	 * 
	 * @param time 时间，毫秒为单位
	 * @param format 要格式的样式
	 * @return
	 * @throws MessageException
	 */
	public static String getFormatTime(long time, String format) throws Exception {

		// 2003-02-28
		// 02:40:48yyyy-MM-dd HH:mm:ss
		// HH:mm:ss
		try {
			SimpleDateFormat formatter = new SimpleDateFormat(format);
			Date currentTime_1 = new Date(time);
			format = String.valueOf(formatter.format(currentTime_1));
		} catch (Exception e) {
			_log.error("", e);
			throw e;
		}
		return format;
	}

	/**
	 * 得到今天的开始毫秒数
	 * 
	 * @return
	 * @throws MessageException
	 */
	public static long getTodyMillisecond() {
		Calendar clen = Calendar.getInstance();
		int time = (clen.get(Calendar.HOUR_OF_DAY)) * 3600 * 1000 + clen.get(Calendar.MINUTE) * 60 * 1000;
		return System.currentTimeMillis() - ((long) time);
	}
	/**
	 * 在当前日期上加年，月，日
	 * @param dateVal   数�?
	 * @param dateType  类型 y:年，M:�?d:�?
	 * @return
	 */
	public static java.sql.Timestamp getDate(int dateVal,String dateType) {
        try {
            java.text.SimpleDateFormat myFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
            Calendar cl = Calendar.getInstance();
            if("y".equals(dateType)){
            	 cl.add(Calendar.YEAR, dateVal);
            }else if("M".equals(dateType)){
            	cl.add(Calendar.MONTH, dateVal);
            }else if("d".equals(dateType)){
            	cl.add(Calendar.DATE, dateVal);
            }
             java.util.Date date = cl.getTime();
            String mystrdate = myFormat.format(date);
            return java.sql.Timestamp.valueOf(mystrdate);
        }
        catch (Exception e) {
        	e.printStackTrace();
            return null;
        }
    }
	/**
	 * 得到日期字符串，包括毫秒
	 * @return
	 */
	public static String getNowDateStr(){
		java.text.SimpleDateFormat myFormat = new SimpleDateFormat("yyyyMMddhhmmssSSS");
		Date date=new Date(System.currentTimeMillis());
		return myFormat.format(date);
	}

	/**
	 * 替换正则表达式字�?主要用于replaceAll
	 * 
	 * @param text
	 * @return
	 */
	public static String replaceRegexText(String text) {
		if (text == null) return text;
		text = Tools.replaceText(text, "\\", "\\\\");
		text = Tools.replaceText(text, ")", "\\)");
		text = Tools.replaceText(text, "*", "\\*");
		text = Tools.replaceText(text, "(", "\\(");
		text = Tools.replaceText(text, "+", "\\+");
		text = Tools.replaceText(text, "|", "\\|");
		text = Tools.replaceText(text, "{", "\\{");
		text = Tools.replaceText(text, "}", "\\}");
		text = Tools.replaceText(text, "[", "\\[");
		text = Tools.replaceText(text, "]", "\\]");
		text = Tools.replaceText(text, "\"", "\\\"");
		text = Tools.replaceText(text, "$", "\\$");
		// text = Tools.searchReplace(text, ".", "\\.");
		// text = Tools.searchReplace(text, "?", "\\?");

		return text;
	}

	/**
	 * 替换�?��的正则表达式字符
	 * 
	 * @param text
	 * @return
	 */
	public static String replaceAllRegexText(String text) {
		if (text == null) return text;
		text = Tools.replaceText(text, "\\", "\\\\");
		text = Tools.replaceText(text, ")", "\\)");
		text = Tools.replaceText(text, "*", "\\*");
		text = Tools.replaceText(text, "(", "\\(");
		text = Tools.replaceText(text, "+", "\\+");
		text = Tools.replaceText(text, "|", "\\|");
		text = Tools.replaceText(text, "{", "\\{");
		text = Tools.replaceText(text, "}", "\\}");
		text = Tools.replaceText(text, "[", "\\[");
		text = Tools.replaceText(text, "]", "\\]");
		text = Tools.replaceText(text, "\"", "\\\"");
		text = Tools.replaceText(text, "$", "\\$");
		text = Tools.replaceText(text, ".", "\\.");
		text = Tools.replaceText(text, "?", "\\?");

		return text;
	}

	/**
	 * url编码
	 * 
	 * @param url
	 * @return
	 * @throws MessageException
	 */
	public static String urlEncode(String url) {
		if (url == null) return "";
		StringBuffer result = new StringBuffer();
		int i = 0;
		byte c;

		char[] ENCODE_TABLE = new char[] { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
		byte[] bytes = url.getBytes();

		try {
			for (i = 0; i < bytes.length; i++) {
				c = bytes[i];
				if ((c >= '0' && c <= '9') || (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z')) {
					result.append((char) c);
				} else {
					result.append('%');
					result.append(ENCODE_TABLE[(c >> 4) & 0x0f]);
					result.append(ENCODE_TABLE[c & 0x0f]);
				}
			}
			ENCODE_TABLE = null;
		} catch (Exception e) {
			_log.error("", e);
		}
		return result.toString();
	}

	/**
	 * 替换正则表达式中�?为\\$,用于StringBuffer.appendReplacement
	 * 
	 * @param text
	 * @return
	 */
	public static String replaceRegexMoneyString(String text) {
		return Tools.replaceText(text, "$", "\\$");
	}

	/**
	 * 替换字符�?
	 * 
	 * @param source 字符�?
	 * @param oldStr 旧的字符
	 * @param newStr 新的字符
	 * @return
	 */
	public static String replaceText(String source, String oldStr, String newStr) {
		if (source == null) return source;
		StringBuffer bf = new StringBuffer(source);
		int flag = bf.indexOf(oldStr);
		int oldLen = oldStr.length();
		int newLen = newStr.length();
		while (flag != -1) {
			bf.replace(flag, flag + oldLen, newStr);
			flag = bf.indexOf(oldStr, flag + newLen);
		}
		return bf.toString();
	}
	public static String getFileUrl(HttpServletRequest request, String path){
		String url = "";
		url = request.getScheme() + ":" + "//" + request.getServerName() +":" + request.getServerPort() +request.getContextPath() + path;
		return url;
	}
}
